﻿using System;

namespace xEngine.DataTypes
{
    public abstract class QuadTreeNode
    {
        #region Enums

        public static class NodePosition
        {
            public const int SingleNode = -1;
            public const int TopLeft = 0;
            public const int TopRight = 1;
            public const int BottomLeft = 2;
            public const int BottomRight = 3;
        }
        public static class NeighborPosition
        {
            public const int Top = 0;
            public const int Right = 1;
            public const int Left = 2;
            public const int Bottom = 3;
        }

        #endregion
    }
    public abstract class QuadTreeNode<TNode, TTree> : QuadTreeNode
        where TNode : QuadTreeNode<TNode, TTree>
        where TTree : QuadTree<TNode, TTree> 
    {
        #region Member Variables
        #endregion

        #region Properties

        public TTree ParentTree { get; set; }
        public TNode ParentNode { get; set; }

        public bool HasChildren
        {
            get
            {
                return Children[0] != null && Children[1] != null && Children[2] != null && Children[3] != null;
            }
        }

        public int Depth
        {
            get
            {
                int depth = 1;

                if(ParentNode != null)
                    depth += ParentNode.Depth;

                return depth;
            }
        }

        public TNode[] Children { get; protected set; }
        public TNode[] Neighbors { get; protected set; }

        public int Position { get; protected set; }

        #endregion

        #region Constructors

        public QuadTreeNode()
        {
            Children = new TNode[4];
            Neighbors = new TNode[4];
        }

        #endregion

        #region Functions

        public int FindMaxDepth()
        {
            int depth = 1;

            if(HasChildren)
                depth += Children[0].FindMaxDepth();

            return depth;
        }

        #endregion
    }
}